package com.vf.cloud.server.mongodb.server;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.TimerTask;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import com.jfinal.kit.StrKit;
import com.vf.cloud.pass.common.constant.SoftPath;
import com.vf.cloud.pass.common.util.ProssUtil;

import lombok.extern.slf4j.Slf4j;

@Slf4j
public class Server implements Runnable{
	
	private boolean isRun=false;
	
	@Override
	public void run() {
		try {
			
			String MongodbPid = ProssUtil.getPid("27018");
			if (!StrKit.isBlank(MongodbPid)) {
				log.info("MongodbServer >>> 启动Mongodb成功>>pid:" + MongodbPid);
				ProssUtil.put("MongodbServer", MongodbPid);
				isRun=true;
			}else {
				File f = new File(String.format("%s/mongodb/bin/mongod.conf", SoftPath.path));
				if(!f.exists()) {
					if(writeConfig()) {
						
						File fdata=new File(String.format("%s/mongodb/data", SoftPath.path));
						if(!fdata.exists()) {
							fdata.mkdir();
						}
						
						File flog=new File(String.format("%s/mongodb/log", SoftPath.path));
						if(!flog.exists()) {
							flog.mkdir();
						}
						
						String cmd=String.format("%s/mongodb/bin/mongod.exe -f \"%s/mongodb\\bin\\mongod.conf\"", SoftPath.path,SoftPath.path);
						int status = executeCmd(cmd);
						if (0 == status) {
							check(true);
						}
					}
				}else {
					
					File fdata=new File(String.format("%s/mongodb/data", SoftPath.path));
					if(!fdata.exists()) {
						fdata.mkdir();
					}
					
					File flog=new File(String.format("%s/mongodb/log", SoftPath.path));
					if(!flog.exists()) {
						flog.mkdir();
					}
					
					String cmd=String.format("%s/mongodb/bin/mongod.exe -f \"%s/mongodb\\bin\\mongod.conf\"", SoftPath.path,SoftPath.path);
					int status = executeCmd(cmd);
					if (0 == status) {
						check(false);
					}
				}
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	
	
	public boolean isRunning() {
		while(true) {
			try {
				if(isRun) {
					break;
				}
				Thread.sleep(1000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
		}
		return isRun;
	}
	
	/**
	 * 写入配置文件
	 */
	public boolean writeConfig() {
		BufferedWriter out = null;
		try {
			File f = new File(String.format("%s/mongodb/bin/mongod.conf", SoftPath.path));
			if (f.exists()) {
				f.delete();
			}
			
			out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(f, true)));
			Map<String,Object> prop=new HashMap<String,Object>();
			prop.put("dbpath", String.format("%s/mongodb/data", SoftPath.path));
			prop.put("logpath", String.format("%s/mongodb/log/mongodb.log", SoftPath.path));
			prop.put("logappend", "true");
			prop.put("port", "27018");
			prop.put("auth", "false");
			prop.put("bind_ip", "0.0.0.0");
			prop.put("journal", "true");
			prop.put("quiet", "true");
			prop.put("notablescan", "false");
			
			Iterator<String> it=prop.keySet().iterator();
			while(it.hasNext()) {
				String key=it.next();
				Object value=prop.get(key);
				out.write(key+"="+value + "\r\n");
			}
			try {
				out.close();
			} catch (IOException e) {
			}
			return true;
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			try {
				out.close();
			} catch (IOException e) {
			}
		}
		return false;
	}

	private int executeCmd(String command) throws IOException {
		try {
			Runtime runtime = Runtime.getRuntime();
			Process process = runtime.exec("cmd /c start /b " + command);
			new Thread(
					new ConsoleThread(new BufferedReader(new InputStreamReader(process.getInputStream(), "UTF-8"))))
							.start();
			return process.waitFor();
		} catch (InterruptedException e) {
		}
		return -1;
	}

	class ConsoleThread implements Runnable {
		private BufferedReader bfr = null;
		public ConsoleThread(BufferedReader bfr) {
			this.bfr = bfr;
		}

		@Override
		public void run() {
			String line = null;
			try {
				while ((line = bfr.readLine()) != null) {
					log.info(line);
				}
			} catch (IOException e) {
				e.printStackTrace();
			}
		}

	}
	
	private ScheduledExecutorService scheduledExecutor = Executors.newScheduledThreadPool(1);
	public void check(boolean isInstall) {
		scheduledExecutor.scheduleWithFixedDelay(new TimerTask() {
			@Override
			public void run() {
				String MongodbPid = ProssUtil.getPid("27018");
				if (!StrKit.isBlank(MongodbPid)) {
					log.info("MongodbServer >>> 启动MongodbServer成功>>pid:" + MongodbPid);
					ProssUtil.put("MongodbServer", MongodbPid);
					if(isInstall) {
						create();
					}else {
						isRun=true;
					}
					scheduledExecutor.shutdown();
				}

			}
		}, 0, 1, TimeUnit.SECONDS);
	}
	
	public void create() {
		try {
			Runtime runtime = Runtime.getRuntime();
			String cmd=String.format("%s/mongodb/bin/mongo --port 27018 < %s/mongodb/bin/operate.txt",SoftPath.path,SoftPath.path);
			Process process = runtime.exec("cmd /c " + cmd);
			BufferedReader br = new BufferedReader(new InputStreamReader(process.getInputStream(), "UTF-8"));
			String line = null;
			while ((line = br.readLine()) != null) {
				log.info(line);
			}
			
			isRun=true;
		} catch (Exception e) {
		}
	}

}
